package com.anyisn.anyflickr.modules.PhotosSlide.view.component
{
	import com.adobe.webapis.flickr.Photo;
	import com.anyisn.anyflickr.common.events.PhotoLoadEvent;
	import com.anyisn.flickr.as3.utils.Urls;
	
	import flash.display.Bitmap;
	import flash.display.BitmapData;
	import flash.display.Loader;
	import flash.events.Event;
	import flash.events.IOErrorEvent;
	import flash.events.MouseEvent;
	import flash.events.ProgressEvent;
	import flash.events.TimerEvent;
	import flash.geom.Point;
	import flash.net.URLRequest;
	import flash.net.sendToURL;
	import flash.ui.Mouse;
	import flash.utils.Timer;
	
	import mx.core.UIComponent;
	
	[Event(name="photoAdded", type="flash.events.Event")]
	[Event(name="slideStarted", type="flash.events.Event")]
	[Event(name="slidePaused", type="flash.events.Event")]
	[Event(name="slideContinued", type="flash.events.Event")]
	[Event(name="slideEnded", type="flash.events.Event")]
	
	public class PhotosSlideUI extends UIComponent
	{
		public function PhotosSlideUI()
		{
			super();
			_loader = new Loader();
			_loader.contentLoaderInfo.addEventListener(Event.OPEN, photoLoadOpen);
			_loader.contentLoaderInfo.addEventListener(Event.COMPLETE, photoLoaded);
			_loader.contentLoaderInfo.addEventListener(IOErrorEvent.IO_ERROR, photoIOError);
			_loader.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS, photoProgress);
			_loadingPhotos = false;
			_loadingPhoto = false;
			_isError  = false;
			_allowPhotoLoading = true;
			_timeOut = true;
			_dissolving = false;
			addEventListener(MouseEvent.CLICK, showPhotoInfoWin);
			_showed = new Array();
		}
		
		public function startSlide():void {
			_bitmapArray = [];
			_i = 0;
			_j = -1;
			_loadingPhotos = true;
			load(_photos[_i]);
			dispatchEvent(new Event("slideStarted"));
		}
		
		private function pauseSlide():void {
			_allowPhotoLoading = false;
			if(_loadingPhoto) {
				_loader.close();
				_loader.unload();
				_loadingPhoto = false;
				_loadingPhotos = false;
				_i--;
			}
			_timer.stop();
			dispatchEvent(new Event("slidePaused"));
		}
		
		private function continueSlide():void {
			_allowPhotoLoading = true;
			if(_i+1<_photos.length) {
				_i++;
				_loadingPhotos = true;
				load(_photos[_i]);
			}
			showNextPhoto();
			dispatchEvent(new Event("slideContinued"));
		}
		
		public function tooglePause():void {
			if(_allowPhotoLoading) {
				pauseSlide();
			} else {
				continueSlide();
			}
		}
		
		private function load(photo:Photo):void {
			if(_allowPhotoLoading) {
				var url:String = Urls.getPhotoSrc(photo);
				_loader.load(new URLRequest(url));
			} else {
				_loadingPhotos = false;
			}
		}
		
		private function photoLoadOpen(e:Event):void {
			_loadingPhoto = true;
		}
		
		private function photoProgress(e:ProgressEvent):void {
			
		}
		
		private function photoLoaded(e:Event):void {
			_loadingPhoto = false;
			_bitmapArray[_i] = _loader.content as Bitmap;
			_loader.unload();
			if(_i==_j+1 && _timeOut) {
				_timeOut = false;
				showPhoto(_i);
			}
			if(_i+1<_photos.length) {
				_i++;
				load(_photos[_i]);
			} else {
				_loadingPhotos = false;
			}
		}
		
		private function showPhoto(i:int):void {
			_next_j = i;
//			var bitmap:Bitmap = _bitmapArray[i];
//			bitmap.addEventListener(Event.ADDED, beginFadeIn);
//			bitmap.addEventListener(Event.ADDED, beginResize);
			var bm_1:Bitmap;
			if(this.numChildren == 0) {
				_bmd_1 = new BitmapData(500,500,true,000000);
				bm_1= new Bitmap(_bmd_1);
				addChild(bm_1);
			} else {
				bm_1 = this.getChildAt(0) as Bitmap;
			}
			_bmd_2 = _bitmapArray[_next_j].bitmapData;
			_seed = Math.random()*10000;
			this.width = _bmd_2.width;
			this.height = _bmd_2.height;
			this.addEventListener(Event.ENTER_FRAME, onEnterFrame);
			_dissolving = true;
			beginResize();
			_frames_left = stage.frameRate*1;
			_pixelsPerFrame = _bmd_2.width*_bmd_2.height/_frames_left;
			
/*			if(this.numChildren == 1) {
				this.removeChildAt(0);
			}
			this.width = bitmap.width;
			this.height = bitmap.height;
			this.addChild(bitmap);*/
		}
		
		private function showPhotoInfoWin(e:MouseEvent):void {
			if(_j>-1 && !_showed[_j]) {
				dispatchEvent(new PhotoLoadEvent(PhotoLoadEvent.LOAD_PHOTO_SUCCESS, _photos[_j], _bitmapArray[_j], true));
				_showed[_j] = true;
			}
		}
		
		private function onEnterFrame(e:Event):void {
			_seed = _bmd_1.pixelDissolve(_bmd_2, _bmd_2.rect, new Point(), _seed, _pixelsPerFrame);
			_frames_left--;
			if(_frames_left==0){
				this.removeEventListener(Event.ENTER_FRAME, onEnterFrame);
				_j = _next_j;
				_timer.stop();
				_timer.start();
			}
		}
		
		private function showNextPhoto(e:Event = null):void {
			if(_j+1<_photos.length) {
				if(_i==_j+1 && _loadingPhotos) {
					_timeOut = true;
				} else if(_bitmapArray[_j+1] == null) {
					_j++;
					showNextPhoto();
				} else {
					showPhoto(_j+1);
				}
			} else {
				_j = -1;
				showNextPhoto();
			}
		}
		
/*		private function beginFadeIn(e:Event):void {
			if(_allowPhotoLoading) {
				var bitmap:Bitmap = e.target as Bitmap;
				bitmap.removeEventListener(Event.ADDED, beginFadeIn);
				_fadeIn.end();
				_fadeIn.target = bitmap;
				_fadeIn.play();
			}
		}*/
		
		private function beginResize(e:Event = null):void {
			if(_allowPhotoLoading) {
				if(e) {
					var bitmap:Bitmap = e.target as Bitmap;
					bitmap.removeEventListener(Event.ADDED, beginResize);
				}
				dispatchEvent(new Event("photoAdded"));
			}
		}
		
		private function photoIOError(e:IOErrorEvent):void {
			_loadingPhoto = false;
			_isError = true;
			_bitmapArray[_i] = null;
			_loader.unload();
			if(_i+1<_photos.length) {
				_i++;
				load(_photos[_i]);
			}
		}
		
		public function clear():void {
			_timer.stop();
			_timer.removeEventListener(TimerEvent.TIMER_COMPLETE, showNextPhoto);
			_timer = null;
			_bitmapArray = null;
			_allowPhotoLoading = false;
			if(_loadingPhoto) {
				_loader.close();
				_loader.unload();
				_loadingPhoto = false;
			}
			if(_dissolving)
				_frames_left = 1;
			removeEventListener(MouseEvent.CLICK, showPhotoInfoWin);
		}
		
		public function set photos(value:Array):void {
			_photos = value;
/*			_fadeIn = new Fade();
			_fadeIn.alphaFrom = 0;
			_fadeIn.alphaTo = 1;
			_fadeIn.duration = 500;*/
			if(_delay)
				startSlide();
		}
		
		public function set delay(value:int):void {
			_delay = value;
			_timer = new Timer(_delay * 1000, 1);
			_timer.addEventListener(TimerEvent.TIMER_COMPLETE, showNextPhoto);
			if(_photos)
				startSlide();
		}
		
		private var _delay:int;
		private var _photos:Array;
        private var _loader:Loader;
        private var _timer:Timer;
        private var _loadingPhoto:Boolean;
        private var _loadingPhotos:Boolean;
        private var _isError:Boolean;
        private var _bitmapArray:Array;
        private var _i:int; // 待load的bitmap index
		private var _next_j:int; // 待add的bitmap index
        private var _j:int; // 已add的bitmap index
        private var _timeOut:Boolean;
//        private var _fadeIn:Fade;
		private var _allowPhotoLoading:Boolean;
		private var _seed:Number;
		private var _bmd_1:BitmapData;
		private var _bmd_2:BitmapData;
		private var _frames_left:int;
		private var _pixelsPerFrame:int;
		private var _dissolving:Boolean;
		private var _showed:Array;
	}
}